package leetcode.editor.cn;

import java.util.ArrayDeque;
import java.util.ArrayList;
import java.util.Deque;
import java.util.List;

/**
* @Author: Dempsey
* @Data: 2021-05-08 09:27:51
*/

//给定两个整数 n 和 k，返回 1 ... n 中所有可能的 k 个数的组合。 
//
// 示例: 
//
// 输入:n = 4, k = 2
//输出:
//[
//  [2,4],
//  [3,4],
//  [2,3],
//  [1,2],
//  [1,3],
//  [1,4],
//] 
// Related Topics 回溯算法 
// 👍 579 👎 0


public class P77{
	public static void main(String[] args) {
		Solution solution = new P77().new Solution();
	}
	
//leetcode submit region begin(Prohibit modification and deletion)
class Solution {
	public List<List<Integer>> combine(int n, int k) {
		// 异常判断
		List<List<Integer>> res = new ArrayList<>();
		if (k <= 0 || n < k) {
			return res;
		}
		// 维护一个队列用于回溯
		Deque<Integer> path = new ArrayDeque<>();
		// 回溯使用dfs
		dfs(n, k, 1, path, res);
		return res;
	}

	private void dfs(int n, int k, int index, Deque<Integer> path, List<List<Integer>> res) {
		if (path.size() == k) {
			res.add(new ArrayList<>(path));
			return;
		}

		// i <= n - (k - path.size()) + 1
		// 后续个数不足的进行剪枝
		for (int i = index; i <= n - (k - path.size()) + 1; i++) {
			path.addLast(i);
			dfs(n, k, i + 1, path, res);
			path.removeLast();
		}
	}
}
//leetcode submit region end(Prohibit modification and deletion)

}